package springcloud.config;


import com.alibaba.druid.pool.DruidDataSource;
import io.seata.rm.datasource.DataSourceProxy;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.mybatis.spring.transaction.SpringManagedTransactionFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;

import javax.sql.DataSource;

/**
 *  * 1. 这里很重要: 配置数据源的代理是 seata 也就是使用 seata代理数据源
 *  * 2. DataSourceProxy 是引入的 io.seata.rm.datasource
 */
@SuppressWarnings("all")
@Configuration
public class DataSourceProxyConfig {


    // 创建属性，并为其赋值。值为 application.yml文件中配置的 mapper.xml文件位置
    @Value("${mybatis.mapperLocations}")
    private String mapperLocations;

    //配置druidDataSource，并注入到容器中
    @Bean
    @ConfigurationProperties(prefix = "spring.datasource")
    public DataSource druidDataSource() {
        return new DruidDataSource();
    }

    //配置DataSourceProxy---使用seata代理数据源
    //该方法的参数是 druidDataSource()方法返回的 druid数据源对象
    @Bean
    public DataSourceProxy dataSourceProxy(DataSource dataSource) {
        return new DataSourceProxy(dataSource);
    }

    //配置SqlSessionFactory---向容器中注入自己创建的SqlSessionFactory实例对象
    //该方法参数 是 dataSourceProxy()方法返回的 DataSourceProxy对象
    @Bean
    public SqlSessionFactory sqlSessionFactoryBean(DataSourceProxy dataSourceProxy) throws Exception {
        //1、创建SqlSessionFactory实例对象
        SqlSessionFactoryBean sqlSessionFactoryBean = new SqlSessionFactoryBean();
        //2、设置数据源为 数据源代理对象
        sqlSessionFactoryBean.setDataSource(dataSourceProxy);
        //3、设置mapper.xml文件位置
        sqlSessionFactoryBean.setMapperLocations(new PathMatchingResourcePatternResolver().getResources(mapperLocations));
        //4、设置事务管理器
        sqlSessionFactoryBean.setTransactionFactory(new SpringManagedTransactionFactory());
        //5、返回SqlSessionFactory实例对象
        return sqlSessionFactoryBean.getObject();
    }
}
